package com.zhouhailin.reflection;

import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;

/**
 * 通过反射机制创建实例
 * 测试 1：通过反射创建某类的对象，要求该类中必须有 public 的无参构造
 * 测试 2：通过调用某个特定构造器的方式，实现创建某类的对象
 *
 * @Author：zhouhailin
 * @Date： 2023/2/13
 */
public class ReflectionCreateInstance {
    public static void main(String[] args) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, InvocationTargetException {

        // 1、获取到User类的Class对象
        Class<?> userClass = Class.forName("com.zhouhailin.reflection.User");
        // 2、通过 public 的无参构造器创建实例
        Object o = userClass.newInstance();
        System.out.println(o);

        // 3、通过 public 的有参构造器创建实例
        // 3.1）先得到对应构造器
        Constructor<?> constructor = userClass.getConstructor(String.class);
        // 3.2）创建实例，并传入实参
        Object name = constructor.newInstance("zhou");
        System.out.println("name = " + name);

        // 4、通过非 public 的有参构造器创建实例
        // 4.1）获取 private 的构造器对象
        Constructor<?> constructor1 = userClass.getDeclaredConstructor(int.class, String.class);
        // 4.2）创建实例
        // 暴破【暴力破解】 , 使用反射可以访问 private 构造器/方法/属性, 反射面前，都是纸老虎
        constructor1.setAccessible(true);
        Object user = constructor1.newInstance(100, "张三丰");
        System.out.println("人物：" + user);

    }
}
